package com.catazy.mvvmlib.net.http

import com.catazy.mvvmlib.base.BaseApplication
import com.catazy.mvvmlib.net.http.interceptor.CacheInterceptor
import com.catazy.mvvmlib.net.http.interceptor.LogInterceptor
import com.franmontiel.persistentcookiejar.PersistentCookieJar
import com.franmontiel.persistentcookiejar.cache.SetCookieCache
import com.franmontiel.persistentcookiejar.persistence.CookiePersistor
import com.franmontiel.persistentcookiejar.persistence.SharedPrefsCookiePersistor
import com.google.gson.GsonBuilder
import me.jessyan.retrofiturlmanager.RetrofitUrlManager
import okhttp3.Cache
import okhttp3.OkHttpClient
import retrofit2.Retrofit
import retrofit2.adapter.rxjava2.RxJava2CallAdapterFactory
import retrofit2.converter.gson.GsonConverterFactory
import java.io.File
import java.util.concurrent.TimeUnit

/**
 * 作者: Tao
 * 日期: 2024/1/29
 * 时间: 10:32
 * 描述: 网络请求构建器基类
 * 主要作用: 添加了一些基础配置，如缓存、超时时间、日志拦截器、Cookies自动持久化等,
 *          1.沿用默认部分配置，并想新增其他配置
 *              可在子类中重写setHttpClientBuilder，setRetrofitBuilder方法,并在方法中调用super
 *          2.完全自定义配置
 *              可在子类中重写setHttpClientBuilder，，不调用super
 */
abstract class BaseNetworkApi {

    private val cookieJar: PersistentCookieJar by lazy {
        PersistentCookieJar(SetCookieCache(), SharedPrefsCookiePersistor(BaseApplication.INSTANCE))
    }

    fun <T> getApi(serviceClass: Class<T>, baseUrl: String): T {
        val retrofitBuilder = Retrofit.Builder()
            .baseUrl(baseUrl)
            .addCallAdapterFactory(RxJava2CallAdapterFactory.create())
            .client(okHttpClient())
        return setRetrofitBuilder(retrofitBuilder).build().create(serviceClass)
    }


    /**
     * 实现重写父类的setHttpClientBuilder方法
     * 在这里可以添加拦截器，可以对 OkHttpClient.Builder 做任意操作
     * 框架默认提供了一组builder,开发者如不想使用默认的配置，可自行继承重写，需要框架的默认配置调用super(builder)
     * 然后自行添加其他配置
     * @param builder OkHttpClient.Builder
     */
    open fun setHttpClientBuilder(builder: OkHttpClient.Builder): OkHttpClient.Builder {
        builder.apply {
            // 设置缓存配置 缓存最大默认10M
            cache(Cache(File(BaseApplication.INSTANCE.cacheDir, "cxk_cache"), 10 * 1024 * 1024))
            //添加Cookies自动持久化
            cookieJar(cookieJar)
            //添加缓存拦截器 可传入缓存天数，不传默认7天
            addInterceptor(CacheInterceptor())
            //日志拦截器
            addInterceptor(LogInterceptor())
            //超时时间 连接、读、写
            connectTimeout(30, TimeUnit.SECONDS)
            readTimeout(15, TimeUnit.SECONDS)
            writeTimeout(15, TimeUnit.SECONDS)
        }
        return builder
    }

    /**
     * 实现重写父类的setRetrofitBuilder方法
     * 在这里可以对Retrofit.Builder做任意操作，比如添加GSON解析器，Protocol
     * 框架默认提供了一组builder,开发者如不想使用默认的配置，可自行继承重写
     * @param builder Retrofit.Builder
     */
    open fun setRetrofitBuilder(builder: Retrofit.Builder): Retrofit.Builder {

        return builder.apply {
            addConverterFactory(GsonConverterFactory.create(GsonBuilder().create()))
        }
    }

    private fun okHttpClient(): OkHttpClient {
        var builder = RetrofitUrlManager.getInstance().with(OkHttpClient.Builder())
        builder = setHttpClientBuilder(builder)
        return builder.build()
    }
}